/*
 * Copyright (c) 2016. For Intelligent Group.
 */

package com.intelligent.mts.da.handler;


import com.intelligent.mts.core.dto.AttributeDto;
import com.intelligent.mts.core.dto.SerialNumberDto;
import com.intelligent.mts.core.service.*;
import com.intelligent.mts.core.utils.AppConst;
import com.intelligent.mts.da.message.ReceiveMessage;
import com.intelligent.mts.da.utils.ApplicationBeanUtils;
import com.intelligent.mts.da.utils.MessageUtils;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelInboundHandlerAdapter;
import io.netty.util.AttributeKey;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.util.Date;

/**
 * Created by Julia.Zhou on 2016/07/20.
 */
public class SaveDataHandler extends ChannelInboundHandlerAdapter {

	public static Logger logger = LoggerFactory.getLogger(SaveDataHandler.class);
	private DataSearchService dataSearchService;

	@Override
	public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {
		logger.info("Start save date process.");
		String returnMessage = "";
		ReceiveMessage receiveMessage = (ReceiveMessage) msg;
		String station = receiveMessage.getStationId();
		try{
			this.setService();
			AttributeKey<ReceiveMessage> attributeKey = AttributeKey.valueOf(AppConst.VALIDATE_DATA);
			ReceiveMessage receiveMessage1 = ctx.channel().attr(attributeKey).get();
			if (receiveMessage1 == null) {
				logger.error("1010 result is NG, you can not continue to do the following process");
				return;
			}  else {
				if (AppConst.STATION_1060.equals(receiveMessage.getStationId())){
					String pn = dataSearchService.findFgPnByParentPrId(receiveMessage1.getProductionId(), AppConst.STATUS_ENABLE);
					if(!receiveMessage.getFgpn().equals(pn)){
						logger.error("FGPN is not correct");
						returnMessage = AppConst.START_DATA_RESP + AppConst.SEPARATOR + station + AppConst.SEPARATOR  + AppConst.RESULT_NG + AppConst.END_FLAG;
						receiveMessage1.setResult(AppConst.RESULT_NG);
					}
					if(receiveMessage.getFgpn().equals(pn)){
						receiveMessage.setProductionId(receiveMessage1.getProductionId());
						returnMessage = this.saveAttributes(receiveMessage);
						logger.info(" 1060 Process finish");
						returnMessage = AppConst.START_DATA_RESP + AppConst.SEPARATOR + station + AppConst.SEPARATOR + returnMessage + AppConst.END_FLAG;
						receiveMessage1.setResult(AppConst.RESULT_OK);
					}
//					ctx.writeAndFlush(returnMessage);
					if (!AttributeKey.exists(AppConst.VALIDATE_DATA)) {
						attributeKey = AttributeKey.newInstance(AppConst.VALIDATE_DATA);
					} else {
						attributeKey = AttributeKey.valueOf(AppConst.VALIDATE_DATA);
					}
					ctx.channel().attr(attributeKey).set(receiveMessage1);
					ctx.fireChannelRead(returnMessage);
				}else{
					Boolean result = MessageUtils.isValidate(receiveMessage, receiveMessage1);
					if (!result) {
						returnMessage = AppConst.START_DATA_RESP + AppConst.SEPARATOR + station + AppConst.SEPARATOR + AppConst.ORDER + "=" + receiveMessage.getOrderId() + AppConst.SEPARATOR + AppConst.RESULT_NG + AppConst.END_FLAG;
					} else {
						returnMessage = this.saveAttributes(receiveMessage);
						returnMessage = AppConst.START_DATA_RESP + AppConst.SEPARATOR + station + AppConst.SEPARATOR + AppConst.ORDER + "=" + returnMessage + AppConst.END_FLAG;
					}
//					ctx.writeAndFlush(returnMessage);
					ctx.fireChannelRead(returnMessage);
					logger.info("Process finish, return:[{}]", returnMessage);
				}
			}
		} catch (Exception e) {
			returnMessage = AppConst.START_DATA_RESP + AppConst.SEPARATOR + station + AppConst.SEPARATOR + AppConst.ORDER + "=" + receiveMessage.getOrderId() + AppConst.SEPARATOR + AppConst.RESULT_NG + AppConst.END_FLAG;
			ctx.writeAndFlush(returnMessage);
			logger.info("Process finish, return:[{}]", returnMessage);
			logger.error("Exception found:[{}]", e.getMessage());
			e.printStackTrace();
		}
	}

	@Override
	public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
		logger.warn("Unexpected exception from com.intelligent.mts.da.handler " + cause);
		ctx.fireExceptionCaught(cause);
	}

	private String saveAttributes(ReceiveMessage receiveMessage) {
		String stationId = receiveMessage.getStationId();
		if (AppConst.STATION_1060.equals(stationId)){
			SerialNumberDto serialNumberDto = new SerialNumberDto();
			serialNumberDto.setStationId(stationId);
			serialNumberDto.setProductionId(receiveMessage.getProductionId());
			serialNumberDto.setSerialName(AppConst.FG_END);
			serialNumberDto.setSerialValue(receiveMessage.getFg());
			serialNumberDto.setPnValue(receiveMessage.getFgpn());
			logger.info("Save Fg serialnumber finish");
			SerialNumberDto serialNumberDto1 = dataSearchService.findCondition(receiveMessage.getProductionId(), stationId, AppConst.FG_END);
			if (serialNumberDto1 != null){
				dataSearchService.updateSerialNumber(serialNumberDto);
				return AppConst.RESULT_OK;
			}
			dataSearchService.createSerialNumber(serialNumberDto);
			return AppConst.RESULT_OK;
		}
		String orderId = receiveMessage.getOrderId();
		logger.info("Save attribute start, orderId:[{}]", orderId);
		String hou = receiveMessage.getHou();
		if (StringUtils.isBlank(hou)) {
			return orderId + AppConst.SEPARATOR + AppConst.RESULT_NG;
		}
		String productionId = dataSearchService.findProductionIdBySerialValue(hou);
		if (StringUtils.isBlank(productionId)) {
			return orderId + AppConst.SEPARATOR + AppConst.RESULT_NG;
		}
		AttributeDto attributeDto = new AttributeDto();
		attributeDto.setProductionId(productionId);
		attributeDto.setStationId(stationId);
		attributeDto.setOderId(receiveMessage.getOrderId());
		attributeDto.setCreateTime(new Date());
		attributeDto.setAttributeValue(receiveMessage.getData());
		dataSearchService.createAttribute(attributeDto);
		logger.info("Save attribute finish.");
		return orderId + AppConst.SEPARATOR + AppConst.RESULT_OK;
	}

	public void setService() {
		if (dataSearchService == null) {
			dataSearchService = ApplicationBeanUtils.getBean(DataSearchService.class);
		}
	}
}
